#pragma once

#include "../CoreMinimal.h"

#include "../NetworkingCommon.h"
#include "google/protobuf/message.h"
#include "../URKProto.h"

#include "BlockEngine/BlockEngineGameMode.h"
#include "Engine/World.h"
#include "BlockEngine/ChunkActor.h"
#include "BlockEngine/DataStructures.h"
#include "../NetworkRW.h"

const MessageHandler message_handler_ServerChunkMessage = [&](google::protobuf::Message* message_primitive) {
	if (message_primitive == NULL) return;
    urk::pb::ServerChunkMessage* message = (urk::pb::ServerChunkMessage *) message_primitive;
	int32 cx = message->x();
	int32 cz = message->z();
	uint8 cy = message->y() & 0xFF;
	ChunkData* chunk_data = new ChunkData();
	/* SIZE_T aaaa = message->mutable_chunk()->size();
	SIZE_T bbbb = message->mutable_chunkdata()->size();
	if (aaaa != 8192 || bbbb != 8192) {
		UE_LOG(URKNetworking, Log, TEXT("Wrong chunk data at (%d, %d, %d) with size (%d, %d)"), cx, cy, cz, aaaa, bbbb);
		return;
	} 
	*/
	for (int x = 0; x < 16*16*16; x++) {
		chunk_data->id[x] = ReadUInt16((void*) message->chunk().data(), x * 2);
		chunk_data->meta[x] = ReadUInt16((void*) message->chunkdata().data(), x * 2);
	}
	ABlockEngineGameMode* gm = ABlockEngineGameMode::GetInstance();
	FFunctionGraphTask::CreateAndDispatchWhenReady([=] {
		FChunkCoordinate coord = FChunkCoordinate{ cx, cz, cy };
		AChunkActor* c = gm->GetWorld()->SpawnActor<AChunkActor>(AChunkActor::StaticClass(), FTransform());
		c->Initialize(coord, chunk_data);

	}, TStatId(), NULL, ENamedThreads::GameThread);
};
